home *** CD-ROM | disk | FTP | other *** search
Text File | 1993-05-23 | 108.3 KB | 3,073 lines |
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- PSK User Manual
-
-
-
- Version 1.3
-
-
-
- Copyright (C) 1993, Geoff Friesen B.Sc.
-
- All rights reserved.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- -1Table of Contents-0
-
-
-
-
-
- Introduction........................................................ 3
-
- Chapter 1 ■ Character Classification and Conversion................ 4
-
- Chapter 2 ■ Critical Error Handler................................. 5
-
- Chapter 3 ■ Data Entry............................................. 8
-
- Chapter 4 ■ Dates..................................................11
-
- Chapter 5 ■ Dialog Box.............................................12
-
- Chapter 6 ■ Event Handling.........................................14
-
- Chapter 7 ■ File and Directory.....................................17
-
- Chapter 8 ■ Game Support...........................................19
-
- Chapter 9 ■ Keyboard and Context-Sensitive Help....................21
-
- Chapter 10 ■ Macros.................................................23
-
- Chapter 11 ■ Message Boxes..........................................24
-
- Chapter 12 ■ Mouse Support..........................................25
-
- Chapter 13 ■ Printing...............................................29
-
- Chapter 14 ■ Security...............................................31
-
- Chapter 15 ■ String Tools...........................................33
-
- Chapter 16 ■ System Query...........................................35
-
- Chapter 17 ■ Video..................................................36
-
- Appendix A ■ Dealing with Errors....................................42
-
- Appendix B ■ DBASE III+ File Format.................................43
-
- Appendix C ■ MAKEDRV................................................45
-
- Appendix D ■ Sample Programs........................................46
-
- Appendix E ■ Installation...........................................48
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- -1Introduction-0
-
-
-
-
-
- Welcome to Programmer's Survival Kit (PSK). PSK is a LARGE-model
-
- library of C functions designed to help you complete a variety of
-
- programming projects quickly and efficiently. Although Borland C++
-
- 3.1 was used to create this library, previous versions of Borland C++
-
- can be used to develop programs with PSK. Turbo C and Turbo C++ can
-
- probably be used as well.
-
-
-
- PSK is shareware. Registration information can be found in the file
-
- PSK.REG. One of the benefits to registering your copy is that you
-
- will receive all of the source code. You can customize PSK to meet
-
- your needs or port it to other compilers.
-
-
-
- Instructions on how to install PSK can be found in Appendix E.
-
-
-
- Several example programs have been written to illustrate the various
-
- functions in this library. These programs are documented in Appendix
-
- D.
-
-
-
- PSK should be used to develop programs that run under DOS 3.30 or
-
- higher. This limitation stems from the fact that the critical error
-
- handler uses a DOS feature that only became available beginning with
-
- version 3.30.
-
-
-
- Version 1.3 differs from its predecessor as follows. The string
-
- toolbox has been expanded. A simple security mechanism for
-
- encrypting/decrypting files has been added. More significantly, this
-
- version introduces a very powerful event handling mechanism which can
-
- be placed at the core of a windowing system. Since windowing systems
-
- rely on mouse support, mouse support has also been added.
-
-
-
- Each version of PSK starting with version 1.1 contains a special
-
- function called "PSKVersion". This function is responsible for
-
- reporting the version number of this library. The version number can
-
- be determined as shown in the following example.
-
-
-
- #include <stdio.H>
-
- #include "psk.H"
-
-
-
- void main (void)
-
- {
-
- int version;
-
-
-
- version = PSKVersion ();
-
- printf ("PSK %d.%d\n", version/16, version%16);
-
- }
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 3 -
-
-
-
-
- -1Chapter 1 ■ Character Classification and Conversion-0
-
-
-
-
-
- Borland C++ contains a variety of macros in CTYPE.H for classifying
-
- characters and converting characters from one case to another. In my
-
- experience, I have found these macros to fail unexpectedly at times.
-
- Therefore, I avoid using them and work with my own functions instead.
-
- CLASSCVT.H contains the prototypes for these functions. In the
-
- following, when I refer to character, I actually mean the ASCII code
-
- of the character.
-
-
-
- -1Prototype-0: int isalnum (int c);
-
-
-
- Test the character passed in "c" to see if it is alphanumeric. Return
-
- nonzero if alphanumeric (0-9, A-Z, a-z) else zero.
-
-
-
- -1Prototype-0: int isalpha (int c);
-
-
-
- Test the character passed in "c" to see if it is alphabetic. Return
-
- nonzero if alphabetic (A-Z, a-z) else zero.
-
-
-
- -1Prototype-0: int isdigit (int c);
-
-
-
- Test the character passed in "c" to see if it is a digit. Return
-
- nonzero if digit (0-9) else zero.
-
-
-
- -1Prototype-0: int islower (int c);
-
-
-
- Test the character passed in "c" to see if it is lowercase. Return
-
- nonzero if lowercase (a-z) else zero.
-
-
-
- -1Prototype-0: int isspace (int c);
-
-
-
- Test the character passed in "c" to see if it is a whitespace
-
- character. A whitespace character is a character having an ASCII code
-
- of 9, 10, 11, 12, 13, or 32. These codes correspond with horizontal
-
- tabs, line feeds, vertical tabs, form feeds, carriage returns, and
-
- spaces. Return nonzero if whitespace else zero.
-
-
-
- -1Prototype-0: int isupper (int c);
-
-
-
- Test the character passed in "c" to see if it is uppercase. Return
-
- nonzero if uppercase (A-Z) else zero.
-
-
-
- -1Prototype-0: int isxdigit (int c);
-
-
-
- Test the character passed in "c" to see if it is hexadecimal. Return
-
- nonzero if hexadecimal (0-9, A-F, a-f) else zero.
-
-
-
- -1Prototype-0: int lower (int c);
-
-
-
- Convert character passed in "c" to lowercase. Return lowercase
-
- equivalent of uppercase character else character.
-
-
-
- -1Prototype-0: int upper (int c);
-
-
-
- Convert character passed in "c" to uppercase. Return uppercase
-
- equivalent of lowercase character else character.
-
-
-
-
- - 4 -
-
-
-
-
- -1Chapter 2 ■ Critical Error Handler-0
-
-
-
-
-
- The Critical Error Handler or CEH as it is also called is a software
-
- routine that attempts to recover from a variety of internal and
-
- external errors that would prevent a program from continuing. It
-
- relys on user input to decide upon a course of action.
-
-
-
- Consider this example. A program wants to open a file and issues the
-
- DOS services interrupt (21h) with the "open file" function code in AH
-
- (3dh). This file is located on a floppy disk that has been inserted
-
- into drive A: but the drive door handle has been left open. What
-
- happens?
-
-
-
- Once interrupt 21h is issued, the DOS kernel takes over. The kernel
-
- calls a device driver. The driver calles the BIOS which communicates
-
- with the disk controller via the IN and OUT machine language
-
- instructions. Because the controller cannot read the disk, it sends
-
- error information to the BIOS which sends this information to the
-
- driver which passes this information on to the DOS kernel. At this
-
- point, the DOS designers could have done one of two things. The
-
- kernel could have always sent the error information to the program
-
- causing it to deal with the error (the FAIL option) or the kernel
-
- could have made an attempt to solve the problem with user help (the
-
- ABORT, RETRY, IGNORE, and sometimes FAIL prompt). This latter
-
- approach was chosen and is more flexible than the previous approach.
-
- The user has the opportunity of closing the door handle and selecting
-
- RETRY. This time, the operation should succeed.
-
-
-
- The ABORT option causes DOS to return to the COMMAND.COM drive prompt.
-
- This option could prove fatal if a file has been opened by the current
-
- program and information has been written to that file but is still
-
- inside a DOS holding buffer. When ABORT is chosen, this buffered
-
- information is not written to disk and the directory entry is not
-
- updated.
-
-
-
- RETRY allows the DOS kernel to attempt the operation again but this
-
- option is generally only useful if the problem is due to leaving a
-
- drive handle open or the printer being offline. In these cases,
-
- closing the door handle or placing the printer online is all that is
-
- needed to get the program running.
-
-
-
- The IGNORE option is a form of gambling. The DOS kernel is told to
-
- ignore the error and let the program continue. If the error is not
-
- too serious then the program will be allowed to continue.
-
-
-
- DOS 3.30 introduced the FAIL option. FAIL informs the kernel that the
-
- program must be allowed to continue but an error code must be returned
-
- for program examination.
-
-
-
- Upon entry to interrupt 24h (the critical error handler), certain
-
- registers contain values indicating the nature of the error and what
-
- course of action needs to be taken. Registers AH, AL, BP:SI, and DI
-
- contain this information.
-
-
-
-
-
-
-
-
-
-
-
-
- - 5 -
-
-
-
-
- If bit 7 of AH is 0 then the error was caused by a disk operation and
-
- is known as a hard error. The failing drive number is placed in AL (0
-
- = A, 1 = B, 2 = C, etc). If bit 5 is 1 then the IGNORE option is
-
- allowed. If bit 4 is 1 then the RETRY option is allowed. If Bit 3 is
-
- 1 then the FAIL option is allowed. FAIL is not allowed on versions
-
- prior to 3.30 and IGNORE may not be allowed on versions 3.30 and
-
- higher because FAIL is present. Bits 2 and 1 contain a code that
-
- indicates the affected disk area. A "00" indicates DOS, a "01"
-
- indicates the file allocation table (FAT), a "10" indicates the
-
- directory, and a "11" indicates the data area. If bit 0 is 1 then the
-
- operation that was taking place when the error occured was a write
-
- otherwise it was a read.
-
-
-
- If bit 7 of AH is 1 then the error was caused by either a character
-
- device such as the printer or a bad memory image of the FAT. BP:SI
-
- points to the device header of the failing device. If the high bit of
-
- the byte at BP:[SI+4] is 1 then the error is due to a bad FAT image
-
- otherwise it is due to a character device. AL contains no useful
-
- information if bit 7 of AH is 1.
-
-
-
- Regardless of what caused the error (disk, device, or bad FAT image),
-
- the lower-half of DI contains one of the following error codes.
-
-
-
- 00h - write-protect violation
-
- 01h - unknown drive number
-
- 02h - drive not ready
-
- 03h - unknown command (to controller)
-
- 04h - CRC data error
-
- 05h - bad request structure length
-
- 06h - seek error
-
- 07h - unknown media (disk) type
-
- 08h - sector not found
-
- 09h - printer out of paper
-
- 0ah - error while writing
-
- 0bh - error while reading
-
- 0ch - general failure
-
-
-
- Upon exit, the CEH returns a code in AL to let the kernel know what
-
- action to take.
-
-
-
- 0 - IGNORE
-
- 1 - RETRY
-
- 2 - ABORT
-
- 3 - FAIL
-
-
-
- Since the CEH is called by the DOS kernel and DOS is not reentrant,
-
- only the following interrupt 21h services can be used from inside the
-
- handler. These services include 01h to 0ch inclusive (the console I/O
-
- services) and 59h (get extended error information). Any other service
-
- will cause the computer to lock up.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 6 -
-
-
-
-
- The default critical error handler is actually located in the resident
-
- portion of the COMMAND.COM program. There are a few problems with
-
- this handler. First, if ABORT is chosen then the current program is
-
- aborted as control returns to the DOS prompt (any data waiting to be
-
- written to disk never arrives). Second, the handler displays a prompt
-
- on screen overwriting the current contents. The critical error
-
- handler located in the CEH module solves both problems. It allows
-
- only two options: RETRY and ABORT. The ABORT option causes a FAIL
-
- code to be returned to the kernel. Therefore, this handler can only
-
- be used with DOS versions 3.30 and higher.
-
-
-
- CEH.H contains the function prototype for the critical error handler
-
- installation function.
-
-
-
- -1Prototype-0: void installceh (void);
-
-
-
- This function installs the critical error handler. It need only be
-
- called once and should be called prior to any disk access.
-
-
-
- This critical error handler consumes a few kilobytes of memory. I
-
- have noticed that it may actually confuse a few users. Therefore, I
-
- decided to create a more streamlined version of the critical error
-
- handler. This handler is installed via the "_installceh" function
-
- (whose prototype is also found in CEH.H). The streamlined CEH does
-
- not display any information on the screen when invoked. The only
-
- action taken is to return a FAIL code to DOS. DOS will then cause the
-
- "failing" interrupt 21h function to return an error code to the
-
- application.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 7 -
-
-
-
-
- -1Chapter 3 ■ Data Entry-0
-
-
-
-
-
- Every database program requires a means of data entry. PSK provides
-
- such a means through the EDIT module. Several data types are
-
- supported.
-
-
-
- Data entry occurs through an entity known as the -1field-0. The field is
-
- a screen area that displays initial and user-entered/user-selected
-
- values. Each one of the _edit functions found in EDIT draws the field
-
- upon entry. Each assumes that the cursor has been positioned to the
-
- left-most column of the field and the video display attribute used in
-
- drawing the field has been selected. Each function takes an -1operation-0
-
- argument. If set to EDIT_DISP, the function exits as soon as the
-
- field is drawn. The NUL value (defined in KBD.H) is returned. If set
-
- to EDIT_FETCH, the function solicits input after drawing the field.
-
- EDIT_DISP is useful in displaying initial values for data entry forms.
-
- EDIT.H contains the function prototypes.
-
-
-
- -1Prototype-0: int _editc (char *c, int width, int operation);
-
-
-
- Display and/or request a character string. A character string is a
-
- string of ASCII characters ending with an ASCII NULL (\0) character.
-
- All characters preceeding the NULL character are restricted to those
-
- having ASCII codes in the range 32 to 126 inclusive. The initial and
-
- final character strings are pointed to by "c". The field width is
-
- passed in "width". The buffer pointed to by "c" must be capable of
-
- holding width+1 characters (the last character is an ASCII NULL). A
-
- variety of editting keys may be used including LEFT, RIGHT, HOME, END,
-
- INS, BS, and DEL. RET, UP, DOWN, and ESC are used to and returned
-
- upon exit. Changes are discarded if ESC is returned otherwise they
-
- are kept.
-
-
-
- -1Prototype-0: int _editd (char *d, int operation);
-
-
-
- Display and/or request a date. A date is a special kind of character
-
- string consisting of exactly eight ASCII digits ending with an ASCII
-
- NULL character. The digits are arranged in YYYYMMDD order. The MM
-
- and DD components start at 01 each and must fall within certain limits
-
- (ex: 01 <= MM <= 12). YYYY can range from 0000 to 9999. The buffer
-
- pointed to by "d" must be capable of holding nine characters (the last
-
- character is an ASCII NULL). The initial value must be a valid date
-
- in YYYYMMDD format. The final value is in this format as well. A
-
- variety of editting keys may be used including HOME, END, and BS.
-
- RET, UP, DOWN, and ESC are used to and returned upon exit. Changes
-
- are discarded if ESC is returned otherwise they are kept. However, If
-
- the user attempts to exit by pressing RET, UP, or DOWN and an invalid
-
- date has been specified then an error message is flashed on the last
-
- row of the screen. The user must press any key to erase this message
-
- and then enter an appropriate date.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 8 -
-
-
-
-
- -1Prototype-0: int _editl (char **l, int *d, int operation);
-
-
-
- Display and/or request a choice string from a list of choice strings.
-
- A choice string is associated with an index relative to zero. The
-
- address of this index is passed in "d". Only the choice string
-
- indexed by "d" is displayed. The user cycles through the list by
-
- pressing the spacebar to move in a forward direction or ALT-spacebar
-
- to move backwards until an appropriate choice string is displayed.
-
- This has the effect of updating the index. The choice list array is
-
- pointed to by "l". The last entry must be a NULL address. RET, UP,
-
- DOWN, and ESC are used to and returned upon exit. If ESC is pressed
-
- then "d" is not updated.
-
-
-
- -1Prototype-0: int _editn (double *n, int width, int dd, int operation);
-
-
-
- Display and/or request a number. The initial and final numbers are
-
- pointed to by "n". The field width is passed in "width". The number
-
- of digits after the decimal point is passed in "dd". The field width
-
- must accomodate the number of decimal digits and the decimal point.
-
- A decimal point may be entered if "dd" is not zero. It should only be
-
- entered once. A variety of editting keys may be used including LEFT,
-
- RIGHT, HOME, END, INS, BS, and DEL. RET, UP, DOWN, and ESC are used
-
- to and returned upon exit. Changes are discarded if ESC is returned
-
- otherwise they are kept.
-
-
-
- -1Prototype-0: int _editp (char *buf, char *pic, int operation);
-
-
-
- Display and/or request a picture string. A picture string is divided
-
- into two parts: data buffer and picture mask. Actual data is obtained
-
- from and placed into the data buffer. The picture mask defines the
-
- way in which the data will appear and what characters can be entered
-
- at each position within the mask. A date is a special kind of picture
-
- string. The data buffer can only hold eight ASCII digits in YYYYMMDD
-
- order but the picture mask causes this data to appear in MM/DD/YYYY
-
- format. Data cannot be entered in the "/" positions. The data buffer
-
- is pointed to by "buf" and the picture mask by "pic". The mask
-
- identifies positions for editable characters and the kind of character
-
- that can be entered at each position (digit or alphabetic). The
-
- buffer must be large enough to hold all editable characters plus an
-
- ASCII NULL character. Any character appearing in "pic" that is not an
-
- "a" or "9" is displayed literally in the field. No editable character
-
- will appear in this position. A variety of editting keys may be used
-
- including HOME, END, and BS. RET, UP, DOWN, and ESC are used to and
-
- returned upon exit. Changes are discarded if ESC is returned
-
- otherwise they are kept.
-
-
-
- HOME moves the cursor to the first editting position and END to the
-
- last. BACKSPACE erases the character in the nearest editting position
-
- to the left of the cursor and repositions the cursor to that position.
-
- DEL erases the character under the current position and moves all
-
- characters to the right one character left. INS toggles between
-
- insert and overwrite modes. A flashing block cursor is displayed if
-
- overwrite mode is in effect.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 9 -
-
-
-
-
- Each one of the _edit functions preserves the cursor shape but not
-
- position.
-
-
-
- -1Prototype-0: void format (char *buf, char *dat, char *pic);
-
-
-
- The "format" function is to "_editp" what "sprintf" is to "printf".
-
- Use "format" to output a picture to a buffer instead of the screen.
-
- The picture mask is pointed to by "pic". The actual data is pointed
-
- to by "dat". The buffer is pointed to by "buf". "Buf" should be the
-
- same size as "pic".
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 10 -
-
-
-
-
- -1Chapter 4 ■ Dates-0
-
-
-
-
-
- The DATE data type is important in database applications. DBASE III+
-
- provides a separate classification for dates in the DBF file format
-
- (see Appendix B). PSK uses the same format as DBASE when dealing with
-
- dates. This format is an eight-digit ASCII string organized as
-
- YYYYMMDD where YYYY represents four year digits, MM represents two
-
- month digits, and DD represents two day digits. DATETIME.H contains
-
- the function prototypes for those functions that work with dates.
-
-
-
- -1Prototype-0: void datei (char *date);
-
-
-
- Increment date by one day. Account for leap years. For example,
-
- datei will correctly advance 19920228 to 19920229 and 19930228 to
-
- 19930301. A valid date in the form YYYYMMDD must be passed via
-
- "date". This will be replaced by the incremented date.
-
-
-
- -1Prototype-0: void datex (char *date, int *year, int *month, int *day);
-
-
-
- Extract year, month, and day components from the date. A valid date
-
- in the form YYYYMMDD must be passed via "date". The year component is
-
- returned via "year", month via "month", and day via "day".
-
-
-
- -1Prototype-0: int doy (char *date);
-
-
-
- Calculate the day of the year that the date falls upon. A valid date
-
- in the form "YYYYMMDD" must be passed via "date". The day of the year
-
- which can range from 1 to 366 inclusive is returned.
-
-
-
- -1Prototype-0: int fday (int year, int month);
-
-
-
- Determine the weekday that the first day of a month falls upon. The
-
- "year" must be greater than or equal to 1583 and the "month" must
-
- range from 1 to 12. Do not use a year beyond 2500 as additional
-
- corrections would probably be required. An integer from 0 through 7
-
- representing a weekday from Sunday to Saturday is returned.
-
-
-
- -1Prototype-0: int isleap (int year);
-
-
-
- Determine if "year" is a leap year. The year should range from 1583
-
- to 2500. A nonzero value is returned if the year is a leap year else
-
- zero is returned.
-
-
-
- -1Prototype-0: int ndays (int month);
-
-
-
- Determine the number of days in a month. The "month" must range from
-
- 1 to 12. If month is 2 (February) then only 28 is returned. The
-
- "isleap" function will be needed to make an adjustment if necessary.
-
- The number of days in the month is returned.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 11 -
-
-
-
-
- -1Chapter 5 ■ Dialog Box-0
-
-
-
-
-
- The dialog box is a close cousin to the message box (see Chapter 11).
-
- Although nowhere near as sophisticated as a graphical user interface
-
- dialog box, the PSK dialog box provides an elegant mechanism for
-
- displaying messages and prompting for a decision via buttons.
-
- DIALOG.H contains the function prototype for the dialog box function.
-
-
-
- A button is a rectangle surrounding a word which indicates a choice.
-
- For example, YES and NO. One of the letters in each word is
-
- highlighted. The highlighted letter is known as a hotkey letter. A
-
- button is selected in one of two ways. Pressing the hotkey letter
-
- selects the button. Pressing this letter a second time closes the
-
- dialog box and returns the hotkey letter to the application. The TAB,
-
- SHIFT TAB, LEFT ARROW, and RIGHT ARROW keys can also be used to select
-
- a button. The RETURN key will close the dialog box and return the
-
- hotkey letter associated with the current button to the application.
-
- The current button is surrounded by a double-line border.
-
-
-
- -1Prototype-0: int dialog (int col, int row, DIALOG *d);
-
-
-
- Display a dialog box described by "d" and await user input. The
-
- dialog box is displayed with its upper-left corner specified by "col"
-
- and "row". If "col" is given a value of -1 then the dialog box is
-
- column-centered. If "row" is given a value of -1 then the dialog box
-
- is row-centered. DIALOG.H contains a typedef for the DIALOG structure
-
- along with a CENTER constant that can be used in centering dialog
-
- boxes.
-
-
-
- typedef struct
-
- {
-
- int ntitles;
-
- char **titles;
-
- int tlattr;
-
- int nchoices;
-
- char **choices;
-
- int chattr;
-
- int *hotkeys;
-
- int hkattr;
-
- int bdattr;
-
- }
-
- DIALOG;
-
-
-
- The ntitles variable refers to the number of titles that are displayed
-
- above the button menu. The titles variable points to an array of
-
- pointers to the title strings. The tlattr variable contains the
-
- attribute used in displaying each title. The nchoices variable refers
-
- to the number of button choices available in the button menu. The
-
- choices variable points to an array of pointers to the button choice
-
- names. The attribute used in displaying all button names is contained
-
- in the chattr variable. Each name can contain a specific character
-
- called a hotkey that, when pressed, selects a button or causes the
-
- dialog box to close and that character to be returned to the
-
- application. The hotkeys variable points to an array of integer
-
- offsets (relative to zero) that identify this hotkey within each
-
- button name. The hkattr variable contains the attribute used in
-
- displaying each hotkey character. The bdattr variable contains the
-
- attribute used in displaying all borders within the dialog box.
-
-
- - 12 -
-
-
-
-
- This function returns -1 if it is unable to allocate dynamic memory.
-
- Otherwise, it returns the hotkey character (converted to uppercase)
-
- associated with the current button. The cursor shape and location are
-
- preserved.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 13 -
-
-
-
-
- -1Chapter 6 ■ Event Handling-0
-
-
-
-
-
- Event handling is an important component of modern user-interface
-
- design. An event is an activity that occurs independently of the
-
- execution of a program. Examples include mouse cursor movements, key
-
- presses, mouse button presses/releases, and timer time-outs. The job
-
- of the event handler is to capture these events and store them in an
-
- event queue where they remain until processed. A queue is a data
-
- structure where information is inserted at one end and removed from
-
- the other. EVENT.H contains the function prototypes for the event
-
- handling functions.
-
-
-
- -1Prototype-0: int e_close (void);
-
-
-
- The "e_close" function shuts down the event handler. This function
-
- must be called before the program can exit otherwise the computer will
-
- be left in an unstable state and will undoubtedly crash. OK is
-
- returned on success or ERROR if the event handler has not been
-
- installed.
-
-
-
- -1Prototype-0: int e_fetch (event *e);
-
-
-
- The "e_fetch" function fetches the next event from the event queue.
-
- It will not return until there is an event waiting to be fetched. The
-
- address of an event structure is passed to this function. It is
-
- composed of five fields. The "type" field identifies which kind of
-
- event occurred: KEY, MOUSE, or TIMER. If a KEY event occurred then
-
- "parm1" contains the ASCII or extended ASCII code of the key that was
-
- pressed. If a MOUSE event occurred then the subevent(s) responsible
-
- for generating a MOUSE event are identified by a list of bit flags
-
- found in "parm1". EVENT.H defines constants beginning with ME_ that
-
- describe these subevents. The state of the mouse buttons can be found
-
- in "parm2". Bit positions 0 and 1 contain the settings for the left
-
- and right mouse buttons respectively. If a three-button Logitech
-
- mouse is being used then bit position 2 has the setting for the middle
-
- button. A zero setting indicates that the button is not currently
-
- being pressed. The cursor column can be found in "parm3" and cursor
-
- row in "parm4". Both values are pixel values. If a TIMER event
-
- occurred then "parm1" contains a value that identifies the timer
-
- responsible for generating the event. OK is returned on success or
-
- ERROR if the event handler has not been installed.
-
-
-
- -1Prototype-0: int e_flush (void);
-
-
-
- The "e_flush" function removes waiting events from the event queue.
-
- OK is returned on success or ERROR if the event handler has not been
-
- installed.
-
-
-
- -1Prototype-0: int e_hide (void);
-
-
-
- The "e_hide" function makes the mouse cursor invisible (unless the
-
- "e_show" function has been called two or more times prior to calling
-
- "e_hide"). This depends on there being an installed mouse driver. OK
-
- is returned on success or ERROR if the event handler has not been
-
- installed.
-
-
-
-
-
-
-
-
- - 14 -
-
-
-
-
-
-
- -1Prototype-0: int e_hook (int (*hook) (int ax, int bx, int cx, int dx),
-
- void (*__mshow) (void), void (*__mhide)
-
- (void));
-
-
-
- The "e_hook" function hooks three functions into the event handler.
-
- The "_hook" function is called whenever a mouse event occurs. The
-
- "__mshow" function is called whenever "e_show" is called and "__mhide"
-
- whenever "e_hide" is called. The purpose of these functions is to
-
- extend the handler in graphics mode to support mouse cursors that are
-
- not supported by the mouse driver. For example, the Hercules and EGA
-
- adaptors are not supported by the Microsoft mouse driver. The "_hook"
-
- function is passed four parameters. AX contains a list of events
-
- defined by bit flags. BX contains the button status. CX and DX
-
- contain the column and row coordinates respectively. A nonzero value
-
- is returned from "_hook" to abort the mouse event. A zero value is
-
- returned otherwise.
-
-
-
- -1Prototype-0: int e_init (int maxevents);
-
-
-
- The "e_init" function installs the event handler. The maximum number
-
- of events that can be stored in the event queue is passed in
-
- "maxevents". If the event queue is full then additional events are
-
- ignored. If the event handler is successfully installed then OK is
-
- returned otherwise ERROR.
-
-
-
- -1Prototype-0: int e_mstatus (int *exist, int *nbuttons);
-
-
-
- The "e_mstatus" function returns the mouse status. If the mouse is
-
- present then "*exist" will be set to a nonzero value otherwise zero
-
- will be used. The number of buttons is passed back to "*nbuttons".
-
- OK is returned on success or ERROR if the event handler has not been
-
- installed.
-
-
-
- -1Prototype-0:int e_resume (void);
-
-
-
- The "e_resume" function resumes event handling after a suspension. OK
-
- is returned on success or ERROR if the event handler has not been
-
- installed.
-
-
-
- -1Prototype-0: int e_settimer (int id, int value);
-
-
-
- The "e_settimer" function initializes and activates a timer. There
-
- are a total of NTIMER timers that may be used. Each timer has an
-
- identifier which is passed in "id". The identifier can range from 0
-
- to NTIMER-1. An initial value is passed in "value" and the timer
-
- begins counting down from this value. Once the timer has reached
-
- zero, a timer event occurs and the timer is reset to this value. OK
-
- is returned on success or ERROR if the event handler has not
-
- been installed or the timer identifier is out of range.
-
-
-
- -1Prototype-0: int e_show (void);
-
-
-
- The "e_show" function makes the mouse cursor visible (unless "e_hide"
-
- has been called two or more times prior to calling "e_show"). This
-
- depends on there being an installed mouse driver. The mouse cursor is
-
- invisible by default. OK is returned on success or ERROR if the event
-
- handler has not been installed.
-
-
-
-
- - 15 -
-
-
-
-
-
-
- -1Prototype-0: int e_srstatus (int *sflag);
-
-
-
- The "e_srstatus" function returns the event handler status by passing
-
- the current status back to "*sflag" (suspension is indicated by a
-
- nonzero value). OK is returned on success or ERROR if the event
-
- handler has not been installed.
-
-
-
- -1Prototype-0: int e_stoptimer (int id);
-
-
-
- The "e_stoptimer" function stops the timer identified by the value
-
- passed in "id" which must range from 0 to NTIMER-1. OK is returned on
-
- success or ERROR if the event handler has not been installed or the
-
- timer identifier is out of range.
-
-
-
- -1Prototype-0: int e_suspend (void);
-
-
-
- The "e_suspend" function suspends the event handler. TIMER, MOUSE,
-
- and KEY events are ignored until the handler is reactivated with
-
- "e_resume".
-
-
-
- -1Prototype-0: int e_tstatus (int id, int *eflag, int *value);
-
-
-
- The "e_tstatus" function returns the status of the timer identified by
-
- the value passed in id which must range from 0 to NTIMER-1. The
-
- enabled status is passed back to "*eflag" (a nonzero value if the
-
- timer is active otherwise zero). The initial value starting the
-
- countdown is passed to "*value". OK is returned on success or ERROR
-
- if the event handler has not been installed or the timer identifier is
-
- out of range.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 16 -
-
-
-
-
- -1Chapter 7 ■ File and Directory-0
-
-
-
-
-
- Certain applications need to know if a file exists prior to performing
-
- some operation. Other applications may need to generate a menu of
-
- file names in a format similar to the DIR command. The ability to
-
- rename directories may also prove to be handy. The following
-
- functions perform these tasks on behalf of the application. FD.H
-
- contains the function prototypes.
-
-
-
- -1Prototype-0: void fde (struct ffblk *de, char *buffer);
-
-
-
- Format a directory entry. The address of an entry block obtained from
-
- "findfirst/findnext" is passed in "de" and the address of a buffer for
-
- holding the result is passed in "buffer". The size of the buffer must
-
- be exactly DESIZE bytes. The result is an ASCIZ string similar to
-
- that produced by the DIR command.
-
-
-
- -1Prototype-0: int fdexist (char *filespec);
-
-
-
- Determine if a file or directory exists. The address of the
-
- file/directory specification is passed in "filespec". A nonzero value
-
- is returned if the file exists.
-
-
-
- -1Prototype-0: int nmdir (char *oname, char *nname);
-
-
-
- Rename a directory. The old name is passed in "oname" and the new
-
- name in "nname". If successful, the directory is renamed and zero is
-
- returned. A -1 is returned if the directory cannot be renamed. This
-
- will be the case if a directory with the same name exists or an
-
- attempt is made to rename a directory located in a different
-
- directory.
-
-
-
- The following example illustrates how "fde" and "fdexist" might be
-
- used. This example displays a list of files in a directory in a
-
- DIR-similar format.
-
-
-
- #include <dir.H>
-
- #include <dos.H>
-
- #include <process.H>
-
- #include <stdio.H>
-
-
-
- #include "fd.H"
-
-
-
- void main (int argc, char **argv)
-
- {
-
- int done;
-
- struct ffblk ffblk;
-
- char buffer [DESIZE];
-
-
-
- if (argc != 2)
-
- {
-
- printf ("invalid command line\n");
-
- exit (1);
-
- }
-
-
-
- if (!fdexist (argv [1]))
-
- exit (1);
-
-
-
-
- - 17 -
-
-
-
-
- printf ("Directory listing of %s\n", argv [1]);
-
- done = findfirst (argv [1], &ffblk, FA_NORMAL);
-
- while (!done)
-
- {
-
- fde (&ffblk, buffer);
-
- puts (buffer);
-
- done = findnext (&ffblk);
-
- }
-
-
-
- exit (0);
-
- }
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 18 -
-
-
-
-
- -1Chapter 8 ■ Game Support-0
-
-
-
-
-
- PSK was not originally designed to support game development. However,
-
- things have changed. PSK now offers support for background music and
-
- joysticks. GAME.H contains function prototypes and useful constants.
-
-
-
- -1Prototype-0: void bmusic (int cmd, ...);
-
-
-
- The "bmusic" function offers background music capability to your
-
- application. This is accomplished by redirecting interrupt 1ch. The
-
- format of the arguments list depends upon the value passed in "cmd".
-
- If BM_OPEN or BM_CLOSE are passed then no additional arguments are
-
- specified. If BM_PLAY is passed then a char * argument pointing to a
-
- song buffer must be specified immediately after "cmd". BM_OPEN must
-
- be passed before passing BM_PLAY. BM_CLOSE must be passed before the
-
- application exits. Play does not begin until BM_PLAY is passed.
-
-
-
- The characters specified in the song buffer must be in ASCII format.
-
- These characters define a language similar to the BASIC PLAY language.
-
- In addition to the notes A, A#, B, C, C#, D, D#, E, F, F#, G, and G#,
-
- the following commands are defined.
-
-
-
- ■ O (set octave)
-
-
-
- Syntax: O#
-
-
-
- Set the current octave to the octave specified by # (# can take on a
-
- value from 1 to 5 inclusive). The default octave is 2 (octave 3
-
- contains middle C).
-
-
-
- ■ L (set note length)
-
-
-
- Syntax: L#
-
-
-
- Set the length of all succeeding notes to that defined by # (# can
-
- take on a value of 1 for whole notes, 2 for half notes, 4 for quarter
-
- notes, 8 for eighth notes, or 6 for sixteenth notes). The default
-
- length is 4 (quarter notes).
-
-
-
- ■ R (reset)
-
-
-
- Syntax: R
-
-
-
- Generate a rest equal to the length of a note using the most recently
-
- specified note length.
-
-
-
- ■ X (cycle)
-
-
-
- Syntax: X
-
-
-
- Reset music to start of the song buffer.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 19 -
-
-
-
-
- ■ S (switch frequency table)
-
-
-
- Syntax: S
-
-
-
- An inverse frequency table has been defined for special effects. This
-
- command toggles back and forth between the inverse and normal
-
- frequency tables.
-
-
-
- ■ 0 (select normal frequency table)
-
-
-
- Syntax: 0
-
-
-
- Select the normal frequency table (the default).
-
-
-
- ■ 1 (select inverse frequency table)
-
-
-
- Syntax: 1
-
-
-
- Select the inverse frequency table.
-
-
-
- -1Prototype-0: int button (void);
-
-
-
- Return the status of the joystick buttons. The status of upto four
-
- buttons is returned simultaneously. A PC can accomodate upto two
-
- joysticks and each joystick has upto two buttons. The constants J1B1,
-
- J1B2, J2B1, and J2B2 defined in GAME.H are used in determining which
-
- button is pressed or not pressed. For example:
-
-
-
- printf ("%d\n", button () & J1B1);
-
-
-
- will display a nonzero value if Joystick 1 Button 1 is currently
-
- pressed. If not pressed then zero would be displayed. This function
-
- can be used with any PC computer equipped with a joystick.
-
-
-
- -1Prototype-0: int joystick (int code);
-
-
-
- Return the current joystick position. The result depends upon the
-
- value passed in "code". A zero causes the X position of joystick 1 to
-
- be returned. A one causes the Y position of joystick 1 to be
-
- returned. A two causes the X position of joystick 2 to be returned.
-
- A three causes the Y position of joystick 2 to be returned. This
-
- function can be used with AT computers and higher. It does not
-
- support PC or XT class machines. I am experimenting with a compatible
-
- technique for these machines and hope to have it available in the next
-
- version of PSK. This function will always return zero no matter what
-
- value is passed in "code" for PC or XT class computers. Any value
-
- passed in "code" which is not in the range 0-3 is treated as 3.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 20 -
-
-
-
-
- -1Chapter 9 ■ Keyboard and Context-Sensitive Help-0
-
-
-
-
-
- PSK contains a keyboard handler with an integrated context-sensitive
-
- help system and a keystroke translation facility. The handler allows
-
- you to fetch keystrokes from and check for the presence of keystrokes
-
- in the BIOS buffer. The help system allows you to install a
-
- context-handler function which is activated whenever the F1 function
-
- key is pressed. A different context can be specified at each point in
-
- the program where keyboard input is required allowing a different help
-
- screen to be displayed when F1 is pressed. You can instruct the
-
- translation facility to substitute certain keystrokes with other
-
- keystrokes. For example, suppose you are designing a data entry form
-
- and want to use the TAB key to switch the input focus from one field
-
- to another. Unfortunately, the data entry functions (see Chapter 3)
-
- do not respond to TAB but they do respond to RET. You can setup a
-
- translation so that RET is returned whenever TAB is pressed.
-
-
-
- KBD.H contains function prototypes, a variety of useful keystroke
-
- constants, and some context-sensitve help constants. These latter
-
- constants all begin with "CTX_" You will notice that two contexts
-
- have been defined: CTX_CEH and CTX_MSG. CTX_CEH is enabled by the
-
- critical error handler upon activation. If a context-handler function
-
- has been established then CTX_CEH will be passed to this function to
-
- identify that F1 has been pressed while the critical error handler is
-
- active. Similarly, if a message box is displayed, CTX_MSG will be
-
- passed to this function. When defining your own context constants,
-
- define them in terms of CTX_USR. I may decide to add several more
-
- predefined context constants in future versions of PSK. If you define
-
- your constants in terms of CTX_USR then you will not need to make
-
- source code changes when working with future versions although a
-
- recompile will be necessary. The example program illustrates how
-
- context-sensitive help is used.
-
-
-
- -1Prototype-0: int k_fetch (void);
-
-
-
- Fetch keystroke. When a key is pressed, the actual value is saved in
-
- an internal variable to be retrieved by another function. The key may
-
- then be translated into another key (even F1 can be translated). If
-
- the result of the translation is F1 and a context-handler function has
-
- been installed and this function is not currently active then the
-
- context-handler function will be called using the most recent context
-
- code. Once you return from the context-handler function, you will
-
- need to press another key. Either the actual keystroke that was
-
- pressed or a translated keystroke is returned.
-
-
-
- -1Prototype-0: void k_flush (void);
-
-
-
- Flush all waiting keystrokes from the BIOS queue. This may have the
-
- effect of invoking the context-handler function. To prevent this,
-
- pass a NULL address to the "k_setctxfunc" function prior to calling
-
- "k_flush" and restore the address afterward.
-
-
-
- -1Prototype-0: int k_getctx (void);
-
-
-
- Return the current context code. A context code is a signed 16-bit
-
- integer.
-
-
-
-
-
-
- - 21 -
-
-
-
-
- -1Prototype-0: int k_iskey (void);
-
-
-
- Determine if a key has been pressed. A nonzero value is returned if a
-
- key was pressed else zero is returned.
-
-
-
- -1Prototype-0: int k_lastkey (void);
-
-
-
- Return the code of the last untranslated keystroke that was pressed
-
- (the default is zero). In the previous example, if TAB was translated
-
- to RET and TAB was pressed, "k_fetch" would return RET but "k_lastkey"
-
- would return TAB.
-
-
-
- -1Prototype-0: void k_setctx (int ctx);
-
-
-
- Set the current context code to "ctx".
-
-
-
- -1Prototype-0: void k_setctxfunc (void (*ctxfunc) (int ctx));
-
-
-
- Set the current context-handler function to "ctxfunc". If NULL is
-
- passed then context-sensitive help is disabled. The default is NULL.
-
-
-
- -1Prototype-0: int k_xtcount (void);
-
-
-
- Return the number of defined translations. The maximum number is 128.
-
-
-
- -1Prototype-0: int k_xtdel (int okey);
-
-
-
- Remove the translation defined for the keystroke specified by "okey".
-
- If the translation was removed then zero is returned. If the key
-
- specified by "okey" could not be found then -1 is returned.
-
-
-
- -1Prototype-0: int k_xtins (int okey, int nkey);
-
-
-
- Establish a translation. The original key is specified by "okey" and
-
- the new key by "nkey". In the previous example, "okey" would be set
-
- to TAB and "nkey" to RET. If a translation already exists based on
-
- "okey" then the translation is updated to reflect the new "nkey". If
-
- the translation was installed then zero is returned. If the maximum
-
- number of translations has been reached then -1 is returned.
-
-
-
- Prototype: int k_xtsize (void);
-
-
-
- Return the maximum size of the translation table. The current size is
-
- 128.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 22 -
-
-
-
-
- -1Chapter 10 ■ Macros-0
-
-
-
-
-
- MACROS.H contains references to two constants, one macro, and an
-
- include file. The ERROR and OK constants can be used by your programs
-
- to establish uniformity. OK is synonymous with zero making it more
-
- efficient to use "if (!value)" instead of "if (value == OK)". The
-
- CENTER macro has been designed to make it easier to center windows and
-
- text on the screen. For example, CENTER(80, strlen ("TITLE")) returns
-
- the centered starting column for TITLE. A reference to STDLIB.H is
-
- made in MACROS.H to allow the min/max macros to be imported. Future
-
- versions of PSK will add more macros to this header.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 23 -
-
-
-
-
- -1Chapter 11 ■ Message Boxes-0
-
-
-
-
-
- A message box is a window that appears at the center of the screen
-
- displaying a message and informing the user as to what keys can be
-
- pressed. When an error occurs, a message box is a convenient way of
-
- informing the user about the error. When a choice must be made, such
-
- as in saving changes, a message box makes it easy to solicit input. A
-
- close cousin to the message box is the message line. A message line
-
- is a line of text that flashes on the last screen row to inform the
-
- user that a time-consuming activity such as sorting or printing is
-
- still in progress. MSG.H contains the function prototypes.
-
-
-
- -1Prototype-0: int msg (int type, char *msg, int bdattr, int txattr);
-
-
-
- The "msg" function implements a message box. The message to be
-
- displayed is pointed to by "msg" and should not exceed 77 characters
-
- (not including the ASCII NULL character). The video attribute used in
-
- displaying the border is passed in "bdattr" and the attribute for
-
- displaying text within the message box is passed in "txattr". The
-
- "type" argument can be one of the three "MSG_" constants defined in
-
- MSG.H. If MSG_AB is passed then the line "PRESS A(Above) OR B(Below)"
-
- is displayed on the last line of the box. If MSG_ANY is passed then
-
- the line "PRESS ANY KEY TO CONTINUE" is displayed on this line. If
-
- MSG_YN is passed then the line "PRESS Y(Yes) OR N(No)" is displayed.
-
- An uppercase A or B is returned if MSG_AB is passed, an uppercase Y or
-
- N is returned if MSG_YN is passed. Any keystroke is returned if
-
- MSG_ANY is passed. The "msg" function saves the current cursor shape,
-
- position and underlying screen contents before displaying the message
-
- box. Upon exit, the cursor shape, position, and screen contents are
-
- restored.
-
-
-
- -1Prototype-0: void msg_flash (int cmd, ...);
-
-
-
- Flash a message on the last screen row. If "cmd" is MSG_FON then a
-
- character string must follow as the second and final argument. This
-
- string will be flashed on the bottom line using a LIGHTGRAY attribute.
-
- If "cmd" is MSG_FOFF then this is the only argument and the screen
-
- contents under this flashing line will be restored removing the line
-
- from the screen. This function cannot be nested because each call
-
- using MSG_FON causes the underlying screen contents to be saved in a
-
- static buffer overwriting the contents of the previous call. An
-
- intervening call using MSG_FOFF is required before a subsequent
-
- MSG_FON.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 24 -
-
-
-
-
- -1Chapter 12 ■ Mouse Support-0
-
-
-
-
-
- The mouse has become a very important input mechanism on PC computers.
-
- Application programs communicate with a mouse via the mouse device
-
- driver. This driver takes over interrupt 33 hexadecimal which serves
-
- as the communications interface. The functions in this library handle
-
- all the interface details with this interrupt. If you intend to use
-
- the event handler functions (see Chapter 6), you will never need to
-
- use most of these functions. Perhaps, in a future version of PSK, I
-
- will provide a more indepth look at the mouse. MOUSE.H contains
-
- function prototypes.
-
-
-
- -1Prototype-0: void mreset (MRESET *resetdata);
-
-
-
- The "mreset" function initializes the mouse and passes back important
-
- information to the calling program via a pointer to an MRESET data
-
- structure. The "exists" field is set to zero if no mouse driver has
-
- been installed. The "nbuttons" field returns the number of mouse
-
- buttons (2 for Microsoft and 3 for Logitech). The internal mouse
-
- handler variables are reset, the scope of operation becomes the full
-
- display, and an invisible mouse cursor is placed on the center of the
-
- screen. The event handler calls this function during installation to
-
- reset the mouse and determine the presence of a mouse driver.
-
-
-
- -1Prototype-0: void mshow (void);
-
-
-
- The "mshow" function makes an invisible mouse cursor visible. This
-
- function and the next control an internal flag. Each time "mshow" is
-
- called, the flag is incremented. The flag is decremented each time
-
- "mhide" is called. Therefore, if "mhide" is called two or more times
-
- before "mshow", "mshow" must be called the same number of times to
-
- restore the cursor visibility. When using the event handler, use
-
- "e_show" instead.
-
-
-
- -1Prototype-0: void mhide (void);
-
-
-
- The "mhide" function makes a visible mouse cursor invisible. Mouse
-
- movement can still occur but the cursor does not appear. Calling
-
- "mshow" at a later time after moving the mouse will show the cursor in
-
- a different location. When using the event handler, use "e_hide"
-
- instead.
-
-
-
- -1Prototype-0: void mpos (MLOCATE *locatedata);
-
-
-
- The "mpos" function returns information about the mouse status (via a
-
- pointer to an MLOCATE data structure). The "buttonstat" field is set
-
- to the status of the mouse buttons. This field is set to the same
-
- values as the "parm2" field of the event structure for a MOUSE event.
-
- The current mouse position is returned in the "col" and "row" fields
-
- (expressed in terms of pixels).
-
-
-
- -1Prototype-0: void mmoveto (int col, int row);
-
-
-
- The "mmoveto" function moves the mouse cursor to the column and row
-
- specified by "col" and "row". These values are expressed in terms of
-
- pixels.
-
-
-
-
-
-
- - 25 -
-
-
-
-
- -1Prototype-0: void mpressed (int button, MLOCATE *locatedata);
-
-
-
- The "mpressed" function returns the mouse pressed status for a button
-
- specified by "button" (a value from 0 to 2). The "opcount" field of
-
- the MLOCATE structure is set to the number of times the button has
-
- been pressed since the last time this function was called. A call to
-
- this function resets this count to zero. The "buttonstat" field is
-
- set to the status of the mouse buttons. The location of the cursor
-
- when the button was last pressed is returned in the "col" and "row"
-
- fields.
-
-
-
- -1Prototype-0: void mreleased (int button, MLOCATE *locatedata);
-
-
-
- The "mreleased" function provides a similar report. It returns the
-
- number of times a mouse button has been released after it was pressed
-
- (0 or 1) via the "opcount" field.
-
-
-
- -1Prototype-0: void mcolrange (int hmin, int hmax);
-
-
-
- The "mcolrange" function sets the horizontal range of the cursor to a
-
- lower limit specified by "hmin" and an upper limit specified by
-
- "hmax". Both values are expressed in pixel positions. The default
-
- value is the entire screen width.
-
-
-
- -1Prototype-0: void mrowrange (int vmin, int vmax);
-
-
-
- The "mrowrange" function sets the vertical range of the cursor to a
-
- lower limit specified by "vmin" and an upper limit specified by
-
- "vmax". Both values are expressed in pixel positions. The default
-
- value is the entire screen height.
-
-
-
- -1Prototype-0: void mgraphcursor (MGCURSOR *gcursordata);
-
-
-
- The "mgraphcursor" function defines the mouse cursor appearance for a
-
- mouse cursor operating in graphics mode. The default graphics cursor
-
- is an arrow pointing in the upper-left direction. A data structure
-
- (MGCURSOR) pointed to by "gcursordata" defines the cursor via the
-
- following fields. The "image" field is a pointer to a pair or masks
-
- defining the cursor appearance. Each mask is defined by an array of
-
- 16-bit unsigned integers. The first 16 define screen mask and the
-
- next 16 define cursor mask. The driver will AND the screen mask with
-
- the display area where the cursor will be placed and then XORs the
-
- result with the cursor mask. This results in a cursor that always
-
- appears in front of whatever is on the display (even when in front of
-
- an object with the same color). The hot spot is a pixel position
-
- within the mask that maps to one pixel on the display. The hot spot
-
- is defined relative to the upperleft corner of the cursor mask. The
-
- driver needs this value to manage the graphics cursor. The column
-
- 0-15 is placed in "hhot". The row 0-15 is placed in "vhot". The
-
- image and hot spot info is needed prior to calling mgraphcursor.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 26 -
-
-
-
-
- -1Prototype-0: void mtextcursor (int cursortype, unsigned arg1,
-
- unsigned arg2);
-
-
-
- The "mtextcursor" function is used to select the type of cursor and
-
- its appearance. The video adaptor's hardware cursor is used when
-
- "cursortype" is given a value of one. A software cursor is used if
-
- zero is passed. The default is the software cursor. A software
-
- cursor's attributes are specified by "arg1" and "arg2". For a cursor
-
- specified as a see-through rectange, 77ffh would be passed in the
-
- "arg1" parameter. If the cursor uses one of the 256 ASCII codes as
-
- its shape then 0 would be passed in "arg1". The MSB of "arg2" is set
-
- to the foreground/background attribute byte and the ASCII code is
-
- placed in the LSB. For example, 0000h and 0718h define a gray
-
- up-arrow cursor. A hardware cursor is simpler to define. Setup
-
- "arg1" and "arg2" as the starting and ending scan lines. The topmost
-
- scan line is always zero. On a monochrome adaptor, 12 is used as the
-
- bottommost scan line. On other adaptors, this value is 7.
-
-
-
- -1Prototype-0: void mmotion (MMOVE *movedata);
-
-
-
- The "mmotion" function returns the net movement of the mouse (given in
-
- mickeys - 1/100 th of an inch) since the last call.
-
-
-
- -1Prototype-0: void minsttask (unsigned mask, unsigned taskseg,
-
- unsigned taskofs);
-
-
-
- The "minsttask" function installs a mouse event handler. The value
-
- passed in "mask" identifies the events that cause the handler to be
-
- activated. The segment and offset addresses of the handler are passed
-
- in "taskseg" and "taskofs" respectively. There is no need for further
-
- discussion because the event handler handles mouse events by
-
- installing a mouse event handler via this function.
-
-
-
- -1Prototype-0: void mlpenon (void);
-
-
-
- The "mlpenon" function activates lightpen emulation (the default).
-
-
-
- -1Prototype-0: void mlpenoff (void);
-
-
-
- The "mlpenoff" function deactivates lightpen emulation.
-
-
-
- -1Prototype-0: void mratio (int horiz, int vert);
-
-
-
- The "mratio" function defines the mickey to pixel ratio. Defaults are
-
- 16 for vertical and 8 for horizontal. This function defines mouse
-
- sensitivity.
-
-
-
- -1Prototype-0: unsigned mbufsize (void);
-
-
-
- The "mbufsize" function returns the size of the buffer needed when
-
- saving the mouse state. The value is the number of bytes.
-
-
-
- -1Prototype-0: void msave (char *buffer);
-
-
-
- The "msave" function saves the current mouse state in "buffer".
-
-
-
-
-
-
-
-
-
-
- - 27 -
-
-
-
-
- -1Prototype-0: void mrest (char *buffer);
-
-
-
- The "mrest" function restores the mouse state from the contents of
-
- "buffer".
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 28 -
-
-
-
-
- -1Chapter 13 ■ Printing-0
-
-
-
-
-
- An important component of any database program is the print manager.
-
- The print manager consists of a set of functions that allow an
-
- application to send information to the printer in a
-
- printer-independent fashion. Some managers also provide background
-
- printing although this capability has yet to be added to the PSK print
-
- manager. You can send individual characters or strings containing
-
- embedded virtual control codes to the print manager where these codes
-
- are translated into appropriate code sequences based on the currently
-
- loaded printer driver before they are issued to the printer. You can
-
- eject pages and determine the number of lines that have been printed.
-
- I will have more to save on printer drivers and virtual control codes
-
- in Appendix C where the MAKEDRV program is discussed. PRINT.H
-
- contains function prototypes and constants for the LPT1, LPT2, and
-
- LPT3 printer ports. You should use these constants in place of
-
- numbers when referencing a printer port in your program.
-
-
-
- -1Prototype-0: int p_char (int c);
-
-
-
- Send the character whose ASCII code is contained in "c" to the print
-
- manager. If a line feed character is sent then an internal lines
-
- printed counter is incremented. If this counter equals the number of
-
- lines per page then the page is ejected and the lines printed counter
-
- is reset to zero. If an error occurs then ESC is returned. If
-
- successful then !ESC is returned.
-
-
-
- -1Prototype-0: int p_eject (void);
-
-
-
- This function is called by "p_char" to eject a page. It does nothing
-
- more than send a form feed character to the print manager and reset
-
- the lines printed counter to zero. If an error occurs then ESC is
-
- returned. If successful then !ESC is returned.
-
-
-
- -1Prototype-0: void p_init (int _lpp, int _port);
-
-
-
- Initialize the print manager. The number of lines per page is passed
-
- in "_lpp". This value is used in determining if a page should be
-
- ejected. The printer port is passed in "_port". You should use one
-
- of the LPT constants defined in PRINT.H when specifying a port.
-
-
-
- -1Prototype-0: int p_lc (void);
-
-
-
- Return the value of the lines printed counter.
-
-
-
- -1Prototype-0: int p_loaddrv (char *_filespec);
-
-
-
- Load a printer driver. A printer driver contains printer specific
-
- codes and virtual codes. When a virtual string is passed to the print
-
- manager, it compares this string to one of the virtual strings in the
-
- driver. If the string is found then the corresponding string of
-
- printer specific codes is output to the printer instead of the virtual
-
- string allowing printer independence for a program. The drive and
-
- path of the driver can be specified as part of "_filespec". If no
-
- extension is specified then .DRV is assumed. If an error occurs then
-
- -1 is returned. If successful then zero is returned.
-
-
-
-
-
-
- - 29 -
-
-
-
-
- -1Prototype-0: void p_sc (int _lp);
-
-
-
- Set the lines printed counter to "_lp". I have never used this
-
- function but decided to include it just in case.
-
-
-
- -1Prototype-0: int p_scandrv (char **drivers);
-
-
-
- Scan the current directory for files ending with a .DRV extension.
-
- Record their names in an internal array and pass the addresses to the
-
- "drivers" array. The array should be capable of holding MAXDRV+1
-
- addresses. If no .DRV files are found then -1 is returned. If more
-
- than MAXDRV .DRV files are found then -2 is returned. If successful
-
- then zero is returned.
-
-
-
- -1Prototype-0: int p_stat (void);
-
-
-
- Return the current printer status (ESC or !ESC).
-
-
-
- -1Prototype-0: int p_str (char *str);
-
-
-
- Send the string of characters pointed to by "str" to the print
-
- manager. The string may contain embedded control codes. A control
-
- code begins with a "^" character and is immediately followed by a
-
- decimal number between 0 and 255 inclusive. An INVALID CONTROL CODE
-
- message will be displayed if no decimal number follows the "^" or the
-
- decimal number is greater than 255. If a "^" is to be sent to the
-
- print manager then it must be doubled (i.e., send "^^"). If an error
-
- occurs then ESC is returned. If successful then !ESC is returned.
-
-
-
- -1Prototype-0: int p_xchar (int c, int count);
-
-
-
- Send upto "count" copies of the character whose ASCII code is
-
- contained in "c" to the print manager. This may result in a page
-
- eject if "c" contains a line feed code and the lines printed counter
-
- equals the number of lines per page. If an error occurs then ESC is
-
- returned. If successful then !ESC is returned.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 30 -
-
-
-
-
- -1Chapter 14 ■ Security-0
-
-
-
-
-
- File security is an important issue in database design. Although many
-
- databases can be conceived without security, there are times when
-
- security is mandatory. For example, a company does not want its
-
- payroll data easily accessible to just anyone.
-
-
-
- I spent alot of time thinking of different techniques for dealing with
-
- security but none seemed satisfactory. The technique should be easy
-
- to implement and relatively transparent to program operation. Most
-
- importantly, the technique must be secure. I chose a two-fold
-
- technique to deal with security.
-
-
-
- This technique involves the creation of file read/write functions that
-
- mirror the standard "fread" and "fwrite" functions. The "s_fread"
-
- function mirrors the "fread" function except that after data is read
-
- from the disk, it is run through a decoder before being passed to the
-
- application. Similarly, the "s_fwrite" function mirrors "fwrite" but
-
- encodes information prior to writing it to the disk.
-
-
-
- The encoding algorithm is fairly straightforward. A byte with an
-
- ASCII code less than 128 is replaced by a byte with an odd-number
-
- ASCII code starting at one. If the ASCII code starts at 128 then this
-
- byte is replaced by a byte with an even-number ASCII code starting at
-
- zero. Here are some examples.
-
-
-
- -------- ----------
-
- Original Translated
-
- -------- ----------
-
-
-
- 0 1
-
- 1 3
-
- 2 5
-
- .............
-
- 125 251
-
- 126 253
-
- 127 255
-
- .............
-
- 128 0
-
- 129 2
-
- 130 4
-
- .............
-
- 253 250
-
- 254 252
-
- 255 254
-
-
-
- Each byte is run through the encoder in three passes. The first pass
-
- uses the original byte as input to the encoder. The output from the
-
- encoder is used as the input for the next two passes.
-
-
-
- Security is maintained as long as this algorithm remains secret.
-
- However, since you now are aware of this algorithm, it cannot be a
-
- secret much longer. You may wish to try some modifications to create
-
- a new secret algorithm. As long as unauthorized persons are not privy
-
- to the algorithm, the data remains hidden (DEBUG, TYPE, and other DOS
-
- commands can be used to view the contents of the file but the data is
-
- undecipherable).
-
-
-
-
- - 31 -
-
-
-
-
- Although the hidden algorithm technique elegantly deals with the
-
- external access problem, there remains the problem of preventing
-
- unauthorized persons from running the program and viewing data. The
-
- solution is to employ a routine to obtain the password and compare the
-
- entered password with a hidden password before giving access. The
-
- password will need to be stored as static data within the program but
-
- it should be stored in some kind of modified state so that the user
-
- cannot peruse the file contents and obtain the password. An algorithm
-
- would be employed to decode this password dynamically. The following
-
- functions implement my security package. SECURITY.H contains function
-
- prototypes.
-
-
-
- -1Prototype-0: size_t s_fread (void *ptr, size_t size, size_t n,
-
- FILE *stream);
-
-
-
- This function is identical to the "fread" function except that the
-
- information is decoded before being sent to the application.
-
-
-
- -1Prototype-0: size_t s_fwrite (void *ptr, size_t size, size_t n,
-
- FILE *stream);
-
-
-
- This function is identical to the "fwrite" function except that the
-
- information is encoded before being sent to the file.
-
-
-
- -1Prototype-0: int s_pmtpwd (char *title, char *pwd);
-
-
-
- This function solicits a password from the user. As the password is
-
- entered, asterisks appear instead of the actual characters the user is
-
- entering. A maximum of ten characters can be entered. A typing
-
- mistake can be corrected by pressing the backspace key.
-
-
-
- The RETURN and ESC keys are used to exit. A beep will sound when
-
- RETURN is pressed and no characters have been entered. This does not
-
- happen if ESC is pressed. RETURN indicates the user wants to try out
-
- the entered password and ESC indicates the user wishes to exit the
-
- program. Only alphanumeric characters are considered as part of the
-
- password.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 32 -
-
-
-
-
- -1Chapter 15 ■ String Tools-0
-
-
-
-
-
- Although the standard C library contains a variety of useful mem...
-
- and str... functions, I needed to invent a few new functions to solve
-
- certain problems. STR.H contains prototypes for these functions.
-
-
-
- -1Prototype-0: void memswap (void *addr1, void *addr2, unsigned n);
-
-
-
- In order to create an efficient sort algorithm for sorting any kind of
-
- data, I needed a generic function for swapping individual elements of
-
- this data. The "memswap" function views memory as an untyped
-
- collection of bytes. By using casts, the addresses of two data
-
- elements being swapped are passed via "addr1" and "addr2" and the size
-
- of an individual element (in bytes) via "n". The C sizeof operator is
-
- useful for calculating the size at compile time.
-
-
-
- -1Prototype-0: char *_strcjust (char *str, int slen);
-
-
-
- Center justify the string "str" by adjusting the leading and trailing
-
- spaces until it is "slen" characters long with the text centered. The
-
- string must have room for at least "slen"+1 characters. The address
-
- of "str" is returned.
-
-
-
- -1Prototype-0: char *_strljust (char *str, int slen);
-
-
-
- Left justify the string "str" by removing leading spaces and padding
-
- with spaces on the right until it is "slen" characters long. The
-
- string must have room for at least "slen"+1 characters. The address
-
- of "str" is returned.
-
-
-
- -1Prototype-0: char *_strltrm (char *str);
-
-
-
- Trim trailing spaces from the string "str". The address of "str" is
-
- returned.
-
-
-
- -1Prototype-0: char *_strpad (char *str, int slen);
-
-
-
- Pad a string "str" with spaces on the right until it is exactly "slen"
-
- characters in length. The string must have room for at least "slen"+1
-
- characters. The address of "str" is returned.
-
-
-
- -1Prototype-0: char *_strrjust (char *str, int slen);
-
-
-
- Right justify the string "str" by removing trailing spaces and padding
-
- with spaces on the left until it is "slen" characters long. The
-
- string must have room for at least "slen"+1 characters. The address
-
- of "str" is returned.
-
-
-
- -1Prototype-0: char *_strtrm (char *str);
-
-
-
- Trim leading spaces from the string "str". The address of "str" is
-
- returned.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 33 -
-
-
-
-
- -1Prototype-0: char *_strxcat (char *dest, char *src, ...);
-
-
-
- Concatenate one or more strings in a single operation. At least one
-
- source string (pointed to by "src") must be specified. As many
-
- strings as necessary can follow "src". The last string must be
-
- followed by NULL. The contents of these strings are stored in a
-
- string pointed to by "dest". The target string must be large enough
-
- to hold the result. The address of "dest" is returned.
-
-
-
- Example:
-
-
-
- #include <stdio.H>
-
- #include <string.H>
-
-
-
- #include "str.H"
-
-
-
- void main (void)
-
- {
-
- int stars_len;
-
- char *hello = "HELLO";
-
- char *world = "WORLD";
-
- char *stars = "***************************************";
-
- char title [80];
-
-
-
- (void) _strxcat (title, hello, " ", world, NULL);
-
-
-
- puts (stars);
-
- puts (_strljust (title, stars_len = strlen (stars)));
-
- puts (_strcjust (title, stars_len));
-
- puts (_strrjust (title, stars_len));
-
- puts (stars);
-
- }
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 34 -
-
-
-
-
- -1Chapter 16 ■ System Query-0
-
-
-
-
-
- The ability to check the current state of a computer is crucial to the
-
- proper operation of applications. For example, an application that
-
- uses graphics needs to know what kind of video adaptor is available.
-
- As another example, an application designed to defragment a disk
-
- should not run if Microsoft Windows is active. This chapter describes
-
- the system query or "sq" functions present in PSK version 1.3. A
-
- video adaptor query function can be found in the next chapter which
-
- deals with video. SQ.H contains function prototypes.
-
-
-
- -1Prototype-0: int sq_dos1 (void);
-
-
-
- Determine if DOS version 1.x is active. A nonzero value is returned
-
- if version 1.x is active otherwise zero is returned.
-
-
-
- -1Prototype-0: int sq_dos5 (void);
-
-
-
- Determine if DOS version 5.0 or higher is active. DOS 5.0 introduced
-
- the SETVER command which allows users to tell DOS to "lie" to certain
-
- applications. These applications are "fooled" into "thinking" that
-
- they are running under a previous version of DOS when in fact they are
-
- running under version 5.0 or higher. This function is not "fooled".
-
- A nonzero value is returned if version 5.0 or higher is active
-
- otherwise zero is returned.
-
-
-
- -1Prototype-0: int sq_dvact (void);
-
-
-
- This function returns a nonzero value if Desqview version 2.0 or later
-
- is active otherwise zero is returned. A robust application should
-
- check for this possibility if there is the chance that the application
-
- will fail when Desqview is active.
-
-
-
- -1Prototype-0: int sq_winact (void);
-
-
-
- This function returns 1 if Windows is running in real or standard
-
- mode, 2 if Windows is running in 386-enhanced mode, or 0 if Windows is
-
- not running. If there is the possiblity that an application will fail
-
- when Windows is running then the application should use this function
-
- to check if Windows is active.
-
-
-
- -1Prototype-0: int sq_xmm (void);
-
-
-
- This function allows an application to determine if an extended memory
-
- manager (such as HIMEM.SYS) is active. A nonzero value is returned if
-
- the XMM is active otherwise zero is returned.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 35 -
-
-
-
-
- -1Chapter 17 ■ Video-0
-
-
-
-
-
- Perhaps the most important component of any computer program is the
-
- user-interface. We have already examined the PSK keyboard interface
-
- in Chapter 9 and now it is time to look at the video interface. The
-
- VIDEO module has been designed to handle text-based video modes as
-
- opposed to graphics-based. An 80-column screen by 25, 43, or 50 rows
-
- is expected (you need an EGA adaptor to work with 43 rows or a
-
- VGA/SVGA adaptor to work with 50 rows). The MDA, CGA, EGA, and
-
- VGA/SVGA video standards are supported.
-
-
-
- One problem associated with the "ancient" CGA adaptor is video
-
- interference that arises when the video circuitry accesses video
-
- memory at the same time that the CPU is accessing this memory. This
-
- interference is commonly known as "snow". Most computers these days
-
- contain VGA or SVGA adaptors although EGA is undoubtedly used on many
-
- as well. Snow is not much of an issue anymore. I did not add any
-
- snow-removal logic to those video functions that interact directly
-
- with video display memory because this would have slowed down the
-
- video system considerably and increased the size of this module.
-
- However, for those of you with CGA adaptors, the following code will
-
- interest you. This code can be used to provide snow removal. You
-
- will need the source code to make these changes (another reason to
-
- register your copy of PSK).
-
-
-
- The MDA and CGA adaptors contain an integrated circuit referred to as
-
- the 6845 CRT controller. This chip has been emulated by the EGA and
-
- VGA/SVGA adaptors so the discussion is relevant to these adaptors as
-
- well. The 6845 contains several internal registers that are accessed
-
- by using the CPU IN and OUT instructions and specifying a port address
-
- that roughly corresponds to a register. The port address 03bah (MDA)
-
- or 03dah (all other adaptors) is directly connected to the STATUS
-
- register. The least significant bit of this register (bit 0) is set
-
- to 1 if it is ok to access video memory or 0 if the video circuitry is
-
- accessing video memory. This bit is referred to as the horizontal
-
- retrace bit because it is a reflection of the video circuitry
-
- horizontal retrace status. The following code segment illustrates how
-
- to monitor the horizontal retrace bit in order to avoid snow. The
-
- code segment assumes that DX contains 03bah and AH contains the video
-
- attribute.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 36 -
-
-
-
-
- @@1:
-
- lodsb ; load next string character
-
- cmp al, 0 ; end of string?
-
- jz @@5 ; yes, exit loop
-
-
-
- cli ; interrupts must be disabled
-
- push ax
-
- @@2:
-
- in al, dx ; wait out current horizontal retrace
-
- shr al, 1 ; there may not be enough time left
-
- jc @@2
-
- @@3:
-
- in al, dx ; wait for next horizontal retrace
-
- shr al, 1
-
- jnc @@3
-
- @@4:
-
- pop ax
-
- stosw ; go ahead and write character
-
- sti ; reenable interrupts
-
- jmp SHORT @@1
-
- @@5:
-
-
-
- VIDEO.H contains function prototypes along with many useful contants
-
- and macros. The screen coordinate system has been setup so that
-
- columns range from 1 to 80 and rows from 1 to 25, 1 to 43, or 1 to 50.
-
-
-
- -1Prototype-0: int v_aa (void);
-
-
-
- Identify the active video adaptor. In the case of EGA and VGA
-
- adaptors, "v_aa" also identifies the kind of monitor connected to the
-
- computer (black & white or color). One of the constants MDA, CGA,
-
- EGA_BW, EGA_COLOR, VGA_BW, or VGA_COLOR is returned.
-
-
-
- -1Prototype-0: int v_attr (char *str, int *attr);
-
-
-
- Display an attribute table and allow the user to select an appropriate
-
- attribute. The UP and DOWN arrow keys are used to select the
-
- background portion of the attribute. The LEFT and RIGHT arrow keys
-
- are used to select the foreground portion. The string pointed to by
-
- "str" is displayed within a window and the color in which it appears
-
- changes as the arrow keys are used to select different attribute
-
- combinations. The length of this string should be such that it fits
-
- within the window. There is no word wrapping. If RET is pressed then
-
- "v_attr" exits with the appropriate attribute returned in "attr". If
-
- ESC is pressed then "v_attr" exits without saving the selected
-
- attribute. RET or ESC is returned.
-
-
-
- -1Prototype-0: void v_border (int style, int x, int y, int nx, int ny);
-
-
-
- Draw a rectangular border on the screen. The upper-left corner is
-
- defined by the "x" and "y" arguments where "x" refers to the column
-
- and "y" to the row. The internal dimensions are defined by the "nx"
-
- and "ny" arguments where "nx" refers to the number of columns and "ny"
-
- refers to the number of rows. The "style" argument is given one of
-
- the defined constants SINGLE_LINE, DOUBLE_LINE, BLOCK_LINE, or
-
- NOBORDER. NOBORDER is used in certain applications that deal with
-
- windows.
-
-
-
-
-
-
- - 37 -
-
-
-
-
- -1Prototype-0: void v_cleanup (void);
-
-
-
- Restore the screen to an appropriate state prior to exitting a
-
- program. The number of screen rows is set to 25, the screen is
-
- cleared to LIGHTGRAY, the cursor is homed, and the cursor is set to a
-
- thin line.
-
-
-
- -1Prototype-0: int v_cputs (const char *str);
-
-
-
- This function is similar to the Borland "cputs" function. The string
-
- pointed to by "str" is displayed starting at the current cursor
-
- position and using the current video attribute. No control codes are
-
- translated. The ASCII code of the last written character is returned.
-
-
-
- -1Prototype-0: void v_cursor (int cmd, ...);
-
-
-
- The "v_cursor" function is used for defining the cursor shape, saving
-
- and restoring the cursor shape, and defining an alternate function for
-
- handling these operations should this function not work on a given
-
- video adaptor.
-
-
-
- 1. v_cursor (CBLOCK);
-
-
-
- The CBLOCK command creates a block cursor shape.
-
-
-
- 2. v_cursor (CHIDE);
-
-
-
- The CHIDE command hides the cursor.
-
-
-
- 3. v_cursor (CLINE);
-
-
-
- The CLINE command creates a line cursor shape.
-
-
-
- 4. v_cursor (CSAVE, &cshape);
-
-
-
- The CSAVE command saves the current cursor shape to the integer
-
- variable cshape.
-
-
-
- 5. v_cursor (CRESTORE, cshape);
-
-
-
- The CRESTORE command restores the cursor shape to cshape.
-
-
-
- 6. v_cursor (CSETFUNC, func, cmdlist);
-
-
-
- The CSETFUNC command installs a function called by "v_cursor" when any
-
- of a combination of commands are passed. The following code fragment
-
- illustrates.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 38 -
-
-
-
-
- void cursor (int cmd, ...);
-
-
-
- ...
-
-
-
- v_cursor (CSETFUNC, cursor, CHIDE | CLINE);
-
-
-
- ...
-
-
-
- void cursor (int cmd, ...)
-
- {
-
- if (cmd == CHIDE)
-
- v_setshape (config.chshape);
-
- else
-
- ...
-
- }
-
-
-
- -1Prototype-0: int v_getattr (void);
-
-
-
- Return the current video attribute.
-
-
-
- -1Prototype-0: int v_getch (void);
-
-
-
- Return the ASCII character code for the character displayed at the
-
- current cursor position.
-
-
-
- -1Prototype-0: int v_getmode (void);
-
-
-
- Return the current video mode.
-
-
-
- -1Prototype-0: int v_getrows (void);
-
-
-
- Return the number of screen rows. This value defaults to 25 but can
-
- be changed with a call to "v_setrows". Several functions call
-
- "v_getrows" to determine the vertical screen size. This makes it easy
-
- to adapt these functions to EGA/VGA adaptors with different vertical
-
- sizes.
-
-
-
- -1Prototype-0: int v_getshape (void);
-
-
-
- Return the current cursor shape. This function should only be used in
-
- functions attached to "v_cursor" for portability reasons. Use the
-
- CSAVE command with "v_cursor" to save the cursor shape.
-
-
-
- -1Prototype-0: void v_gotoxy (int x, int y);
-
-
-
- Position the cursor to the column specified by "x" and the row
-
- specified by "y". The column should range from 1 to 80 and the row
-
- from 1 to the number of screen rows.
-
-
-
- -1Prototype-0: void v_paint (int c, int x, int y, int nx, int ny);
-
-
-
- Paint a rectangular region with upper-left corner defined by "x" and
-
- "y" and dimensions defined by "nx" and "ny". The region is painted
-
- using the character whose ASCII code is in "c" and using the current
-
- video attribute. The "v_clear" macro uses the space character for
-
- clearing a region.
-
-
-
-
-
-
-
-
- - 39 -
-
-
-
-
- -1Prototype-0: int v_putch (int c, int count);
-
-
-
- Put a character whose ASCII code is contained in "c" upto "count"
-
- times on the screen starting at the current cursor position and using
-
- the current video attribute. The ASCII code for "c" is returned.
-
-
-
- -1Prototype-0: int v_putcha (int *ca, int szca);
-
-
-
- This function displays a character/attribute buffer pointed to by "ca"
-
- that contains "szca" entries. Therefore, the buffer does not need to
-
- be NULL terminated. Each entry is composed of an attribute in the
-
- most significant byte and a character ASCII code in the least
-
- significant byte. The value contained in "szca" is returned.
-
-
-
- -1Prototype-0: void v_screen (int cmd, int x, int y, int nx, int ny,
-
- void *buffer);
-
-
-
- Save or restore the screen contents. The region of interest has an
-
- upper-left corner defined by "x" and "y" and dimensions defined by
-
- "nx" and "ny". The SCREEN_SAVE constant is passed in "cmd" to
-
- indicate that the region is to be saved in "buffer". SCREEN_RESTORE
-
- indicates that the contents of "buffer" are to be displayed on the
-
- screen. The buffer must be large enough to accomodate "nx"*"ny"*2
-
- characters.
-
-
-
- -1Prototype-0: void v_scroll (int x, int y, int nx, int ny, int dir,
-
- int nblines, int attr);
-
-
-
- Scroll a rectangular region with upper-left corner defined by "x" and
-
- "y" and dimensions defined by "nx" and "ny" up or down by the number
-
- of lines specified by "nblines". SCROLL_UP is passed via "dir" to
-
- scroll lines upward. SCROLL_DN causes lines to scroll downward. The
-
- video attribute used in displayed blank lines is passed in "attr".
-
-
-
- -1Prototype-0: void v_setattr (int attr);
-
-
-
- Set the current video attribute to the contents of "attr". The
-
- "v_border", "v_cputs", "v_paint", and "v_putch", functions use this
-
- attribute.
-
-
-
- -1Prototype-0: void v_setmode (int mode);
-
-
-
- Set the current video mode. Since the video package supports text
-
- modes only, it is recommended that you use only those modes defined by
-
- constants BW80, C80, and MONO.
-
-
-
- -1Prototype-0: void v_setrows (int _rows);
-
-
-
- Specify the number of screen rows. Currently, only 25, 43, and 50 can
-
- be passed in "_rows". All other values are ignored. The screen is
-
- set to the specified number of rows and the video system makes the new
-
- row size available to all functions that call "v_getrows". If 43 is
-
- passed and a VGA/SVGA adaptor is active then 50 is used. Similarly,
-
- if 50 is passed and an EGA adaptor is active then 43 is used.
-
-
-
-
-
-
-
-
-
-
-
-
- - 40 -
-
-
-
-
- -1Prototype-0: void v_setshape (int shape);
-
-
-
- Set the cursor shape to the contents of "shape". This function should
-
- only be used in functions attached to "v_cursor" for portability
-
- reasons. Use the CBLOCK, CHIDE, and CLINE commands with "v_cursor" to
-
- change the cursor shape.
-
-
-
- -1Prototype-0: int v_setup (int _rows);
-
-
-
- Ensure that the video mode is either BW80, C80, or MONO. Set the
-
- number of screen rows to 25, 43, or 50 as specified by "_rows".
-
- Return the new video mode.
-
-
-
- -1Prototype-0: void v_shadow (int x1, int y1, int nx, int ny);
-
-
-
- Draw a shadow around a rectangular region whose upper-left corner is
-
- specified by "x1" and "y1" and dimensions by "nx" and "ny". This
-
- gives windows a 3D effect.
-
-
-
- -1Prototype-0: int v_wherex (void);
-
-
-
- Return the current cursor column.
-
-
-
- -1Prototype-0: int v_wherey (void);
-
-
-
- Return the current cursor row.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 41 -
-
-
-
-
- -1Appendix A ■ Dealing With Errors-0
-
-
-
-
-
- What is an error? My definition is simple. An error is a flaw. A
-
- compiler generates an error due to a flaw in the syntax of the source
-
- code. A program generates an error through some undesirable behavior
-
- such as locking up the computer due to a flaw in its design. I would
-
- like to consider three sources for these program errors.
-
-
-
- The first source occurs when invalid data is passed to a function.
-
- For example, you decided to save the entire screen contents by calling
-
- the "v_screen" function and passing it the address of a buffer that
-
- can hold 2000 characters. The buffer should actually be capable of
-
- holding 4000 characters since the screen is divided into
-
- character/attribute pairs and each pair occupies two characters. If
-
- you are lucky, nothing serious will happen. However, strange behavior
-
- will undoubtedly occur. Very little in the way of argument checking
-
- is performed by the PSK functions and there is a good reason for this.
-
- Argument checking takes time and can slow down a program. It can also
-
- add to the size of a program. If you are careful about the kind of
-
- data passed via function arguments then no problems will arise. I
-
- have tried to point this out as each function in the library has been
-
- described. Your best bet however is to order the source code.
-
-
-
- The second source comes from not paying close attention to file
-
- input/output return values and not properly closing files. You should
-
- always check the return value when opening a file, reading from a
-
- file, and writing to a file. If the number of characters written does
-
- not correspond to the number requested then something has gone wrong
-
- (probably the disk is full). Never exit a function before closing a
-
- file. This may seem like common sense but there are occasions where I
-
- have spent alot of time trying to track down a mysterious bug only to
-
- find that it arose as a result of not properly closing a file or not
-
- checking a return value.
-
-
-
- The third source deals with dynamic memory allocation. Never assume
-
- that the allocation will succeed. It may return a NULL pointer.
-
- Trying to write data to a NULL pointer is a sure way to crash your
-
- program and reset the computer.
-
-
-
- I hope you find this information useful when writing programs with
-
- PSK. Undoubtedly, it will save you alot of grief.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 42 -
-
-
-
-
- -1Appendix B ■ DBASE III+ File Format-0
-
-
-
-
-
- The DBASE DBF file format is widely used by many database products.
-
- This appendix provides the file format for DBASE III+ DBF files.
-
- However, I have chosen not to go into detail on index files. I'll
-
- leave that to a future version of PSK.
-
-
-
- A DBASE III+ DBF file is used to store database records. This file is
-
- divided into several areas as illustrated. The header contains global
-
- information about this file including the date when it was last
-
- updated and the number of records. The data dictionary describes
-
- every field that is part of the record. A carriage return (CR) byte
-
- ends the data dictionary. Records contain the actual data. A CTRL-Z
-
- byte marks the end of the file. Each record is preceded by an
-
- asterisk byte if it has been marked for deletion otherwise a blank
-
- (ASCII 20h) byte appears.
-
-
-
- ┌────────────┐
-
- │ HEADER │
-
- ├────────────┤
-
- │ DATA │
-
- │ DICTIONARY │
-
- ├────────────┤
-
- │ CR │
-
- ├────────────┤
-
- │ RECORDS │
-
- ├────────────┤
-
- │ CTRL-Z │
-
- └────────────┘
-
-
-
-
-
- -1Header Organization-0
-
-
-
-
-
- Byte 0 Version Number
-
-
-
- This byte holds 03h if no DBT (memo) file is present or 83h if
-
- present.
-
-
-
- Byte 1- 3 Last Update
-
-
-
- These three bytes hold the date when the file was last updated in YY,
-
- MM, DD order. The YY component is calculated by subtracting 1900 from
-
- the current year.
-
-
-
- Byte 4- 7 Header Length
-
-
-
- The number of bytes taken up by the header plus the data dictionary,
-
- and the trailing CR byte is stored here.
-
-
-
- Byte 10-11 Record Length
-
-
-
- The length of a record (including the byte that immediately precedes
-
- the record and indicates whether or not the record has been marked for
-
- deletion) is stored here.
-
-
-
- Byte 12-31 Reserved
-
-
-
-
- - 43 -
-
-
-
-
- -1Data Dictionary Organization-0
-
-
-
-
-
- Each entry in the data dictionary describes one field that makes up a
-
- record and is exactly 32 bytes in length. Upto a maximum of 128
-
- entries can be recorded in the dictionary. The following byte offsets
-
- are relative to the start of an entry.
-
-
-
- Byte 0-10 Field Name
-
-
-
- The field name consists of ASCII characters and is left-justified with
-
- NULL (ASCII 0) bytes padded to the right.
-
-
-
- Byte 11 Field Type
-
-
-
- The field type is an ASCII character describing the kind of data that
-
- can be stored.
-
-
-
- C (character) ASCII characters
-
- N (numeric) - . 0 1 2 3 4 5 6 7 8 9
-
- L (logical) Y y N n T t F f (contains ? when not initialized)
-
- M (memo) 10 digits representing a DBT block number
-
- D (date) 8 digits in YYYYMMDD format
-
-
-
- Byte 12-15 Reserved
-
-
-
- Should be set to 0.
-
-
-
- Byte 16 Field Length
-
-
-
- The length ranges from 0 to 255.
-
-
-
- Byte 17 Field Decimal Count
-
-
-
- The number of digits after the decimal point.
-
-
-
- Byte 18-31 Reserved
-
-
-
- Should be set to 0.
-
-
-
- A memo is a variable-length character string. The actual data for
-
- each memo is kept in a separate file with the same name as the DBF
-
- file but with a DBT extension. I do not know the DBT file format and
-
- am only guessing at the block number but the 10 digits would be ASCII
-
- digits and probably serve as an index into the DBT file.
-
-
-
-
-
- -1Limitations-0
-
-
-
-
-
- 1 billion records maximum
-
- 4000 bytes per record maximum
-
- 128 fields per record maximum
-
- 254 bytes per character field maximum (trailing blanks)
-
- 1 byte per logical field (exactly)
-
- 19 bytes per numeric field maximum
-
- 8 bytes per date field (exactly)
-
- 10 memo fields maximum
-
-
-
-
- - 44 -
-
-
-
-
- -1Appendix C ■ MAKEDRV-0
-
-
-
-
-
- MAKEDRV is a program that I invented to make it easier to create
-
- printer driver files. A driver has a DRV extension. When I first
-
- came up with the concept of drivers, I did not realize that Microsoft
-
- Windows uses DRV as a file extension for its drivers. Therefore, be
-
- warned in advance that you should not mix PSK drivers with Microsoft
-
- Windows drivers.
-
-
-
- The function of a driver is simple. The application program sends a
-
- virtual printer string to the print manager. The print manager looks
-
- up this string in the currently loaded driver. If there is no loaded
-
- driver then the manager sends the string verbatim to the printer. If
-
- there is a loaded driver and the virtual string is not found then the
-
- manager discards the string. It is not sent to the printer. If the
-
- string is found then the real printer string which is also stored in
-
- the driver is sent to the printer instead of the virtual string.
-
-
-
- A virtual string starts with an ESC character (ASCII 27). It is
-
- terminated by a # character. For example, the following is a virtual
-
- string: ^27A#. The ^27 is interpreted as a control code (ESC in this
-
- case). The A serves as an ID code for this string. The # terminates
-
- the string.
-
-
-
- DMP130 and HPLJIII contain the source code for sample drivers. A
-
- driver is divided into one or more lines. The maximum length of a
-
- line is 127 characters. Blank lines can be entered. A comment can
-
- appear anywhere. Comments start with semicolons and all characters
-
- following a semicolon to the end of the line are ignored. The keyword
-
- VIRTUAL is used to indicate the start of a virtual string and must be
-
- placed on a line by itself. The keyword REAL indicates the start of a
-
- real string and also must appear by itself. Following either keyword
-
- is a set of codes on a separate line. Unsigned integers from 0 to 255
-
- can be entered as well as strings of ASCII characters located between
-
- a pair of double quotation marks. Each string can appear on only one
-
- line.
-
-
-
- Some rules need to be followed when writing a source file. The
-
- maximum length of a virtual string including the leading ESC character
-
- is 40 bytes. A virtual string can never include a # character as part
-
- of the string since this character is recognized by the print manager
-
- as a terminator. Therefore, you would never include a # character
-
- with the other characters forming a virtual string. The maximum
-
- number of virtual strings is 32 and real strings is 32. The number of
-
- virtual strings must equal the number of real strings. The maximum
-
- size of a DRV file is 1024 bytes and the minimum size is 16 bytes.
-
-
-
- MAKEDRV is easy to use. The syntax is -1MAKEDRV filespec-0 where filespec
-
- identifies the source file to be converted into a DRV file. The file
-
- is listed line by line to the STDOUT device and error messages are
-
- sent to the STDERR device. MAKEDRV requires DOS 3.30 or higher.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 45 -
-
-
-
-
- -1Appendix D ■ Sample Programs-0
-
-
-
-
-
- Five example programs are included with the PSK library illustrating
-
- the various functions. By studying the source code for each example,
-
- you should get a good idea of how to put these functions together to
-
- build useful programs.
-
-
-
- The first program is a database program called Employee Absence Record
-
- (EAR). EAR is used to keep track of the number of days each employee
-
- in a company is absent for each quarter of a year for different years
-
- between 1990 and 2050 inclusive. If you have an EGA adaptor, you can
-
- run this program in 43-line mode by typing "EAR 43". If you have a
-
- VGA/SVGA adaptor, you can run this program in 50-line mode by typing
-
- "EAR 50". EAR requires DOS 3.30 or higher to run.
-
-
-
- If you are interested in seeing how the critical error handler
-
- functions, copy EAR.EXE and one of the DRV files to a floppy disk.
-
- Insert the disk into one of the floppy drives and then log onto the
-
- drive (make that drive current). Open the door handle and try to load
-
- a file. Press F1 to see the help screen once the critical error
-
- handler appears.
-
-
-
- The scrolling logic is the most complex code in this program. EAR
-
- displays a window in the middle of the screen. This window is used to
-
- display employee names. EAR can support upto 256 employees and hence
-
- display 256 employee names but not all names can appear within this
-
- window at any one time. Therefore, some means of scrolling is needed
-
- to make it possible to view all names. The scrolling logic has turned
-
- out to be the hardest part of the program to write because of the need
-
- to track the lightbar to the appropriate location after inserting or
-
- deleting an employee. For example, suppose you are deleting several
-
- names near the end of the list. Once the first name has been deleted,
-
- the name of the employee that follows will be highlighted. You can
-
- keep pressing DEL until all desired employees have been deleted.
-
- Similarly, when inserting employee names, the lightbar jumps to the
-
- next insert position so you can insert names one right after the
-
- other.
-
-
-
- The second program, called EDEMO, provides a demonstration of the
-
- event handler mechanism. You may wish to elaborate on this code and
-
- turn EDEMO into something more useful.
-
-
-
- The third program is called FILES and lets you play with DOS files.
-
- You can scroll through a list of files, sort them in alphabetical
-
- order, rename files, change directories, etc. FILES provides a good
-
- example of the dialog box function. You can run FILES in EGA 43-line
-
- mode by typing "FILES 43" or in VGA 50-line mode by typing "FILES 50".
-
- Of course, you need an appropriate video adaptor. FILES uses the
-
- streamlined critical error handler. If a critical error occurs, you
-
- will only see a dialog box telling you that a certain action cannot be
-
- performed.
-
-
-
- The fourth program is called JOYDEMO and plays a medly of background
-
- music pieces while scanning the joystick position and button status.
-
- I had planned to write a game to illustrate these features but ran out
-
- of time. Perhaps, the next version of PSK will show something a
-
- little more interesting.
-
-
-
-
- - 46 -
-
-
-
-
- The final program is called SQ and uses the system query functions to
-
- find out certain things about your computer. If you have Windows
-
- capability, try running Windows in standard or 386-enhanced mode and
-
- shell out to DOS via the MSDOS ICON in the MAIN group. What happens
-
- when you run SQ?
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- - 47 -
-
-
-
-
- -1Appendix E ■ Installation-0
-
-
-
-
-
- PSK is distributed in archived form as PSK.ZIP. The following files
-
- are located in this archive.
-
-
-
- README - special instructions on printing PSK.DOC file
-
- PSK.DOC - documentation
-
- PSK.REG - registration information
-
- CEH.H - Critical Error Handler header file
-
- CLASSCVT.H - Classifications and Conversions header file
-
- DATETIME.H - Date & Time Tools header file
-
- DIALOG.H - Dialog Box header file
-
- EDIT.H - Data Entry Editor header file
-
- EVENT.H - Event Handler header file
-
- FD.H - File & Directory header file
-
- GAME.H - Game Tools header file
-
- KBD.H - Keyboard Interface/Context Sensitive Help header file
-
- MACROS.H - Useful Macros
-
- MOUSE.H - Mouse Driver Interface header file
-
- MSG.H - Message Box header file
-
- PRINT.H - Printer Interface header file
-
- PSK.H - PSK Identification header file
-
- SECURITY.H - File Security header file
-
- SQ.H - System Query header file
-
- STR.H - String Management header file
-
- VIDEO.H - Video Interface header file
-
- PSK.LIB - LARGE model version of the PSK C library
-
- EAR.C - Employee Absence Record source file
-
- EAR.PRJ - Employee Absence Record project file
-
- EAR.EXE - Employee Absence Record executable file
-
- EDEMO.C - Event Handler Demonstration source file
-
- EDEMO.PRJ - Event Handler Demonstration project file
-
- EDEMO.EXE - Event Handler Demonstration executable file
-
- FILES.C - DOS Files Tool source file
-
- FILES.PRJ - DOS Files Tool project file
-
- FILES.EXE - DOS Files Tool executable file
-
- JOYDEMO.C - Joystick/Background Music Demonstration source file
-
- JOYDEMO.PRJ - Joystick/Background Music Demonstration project file
-
- JOYDEMO.EXE - Joystick/Background Music Demonstration executable file
-
- SQ.C - System Query Demonstration source file
-
- SQ.PRJ - System Query Demonstration project file
-
- SQ.EXE - System Query Demonstration executable file
-
- MAKEDRV.EXE - MAKEDRV utility program
-
- DMP130 - source code for Tandy DMP 130 printer driver
-
- HPLJIII - source code for HP Laserjet III printer driver
-
- DMP130.DRV - DMP 130 driver
-
- HPLJIII.DRV - Laserjet driver
-
-
-
- Installation is fairly straightforward. The simplest install would be
-
- to copy the .H files into your INCLUDE directory and PSK.LIB into your
-
- LIB directory. You could also make a separate directory called PSK
-
- and copy these files into that directory. You would then need to
-
- setup your INCLUDE and LIB paths to point to this directory. You
-
- might need to change the project files.
-
-
-
-
-
- - 48 -